// Copyright (c) 2022 CHANGLEI. All rights reserved.

import 'dart:math' as math;

import 'package:aircraft_war/bloc/game_state_cubit.dart';
import 'package:aircraft_war/components/aircraft.dart';
import 'package:flame/collisions.dart';
import 'package:flame/components.dart';
import 'package:flame/effects.dart';
import 'package:flame/extensions.dart';

/// Created by changlei on 2022/5/20.
///
/// 奖励
abstract class Supply extends GameStatePositionComponent with CollisionCallbacks {
  /// 子弹补给
  Supply({
    required this.sprite,
    this.speed = 80.0,
    super.size,
    super.anchor,
    super.angle,
    super.position,
    super.scale,
    super.priority,
  });

  late final _effect = RotateEffect.by(
    math.pi / 5,
    InfiniteEffectController(
      ZigzagEffectController(
        period: 4,
      ),
    ),
  );

  /// 图标
  final Sprite sprite;

  /// 初始速度
  final double speed;

  late double _speed = speed;

  /// 增加速度
  void growth(double offset) {
    _speed += offset;
  }

  @override
  Future<void> onLoad() async {
    await add(_effect);
    await add(RectangleHitbox()..collisionType = CollisionType.passive);
  }

  @override
  void render(Canvas canvas) {
    sprite.render(canvas, size: size);
  }

  @override
  void update(double dt) {
    if (gameRef.stateCubit.state != GameState.running) {
      return;
    }
    if (!containsOfParent(position) && !containsOfParent(position + size)) {
      removeFromParent();
      return;
    }
    position.y += _speed * dt;
  }

  @override
  void onNewState(GameState state) {
    switch (state) {
      case GameState.idle:
      case GameState.pending:
      case GameState.stopped:
        removeFromParent();
        break;
      case GameState.pausing:
        _effect.pause();
        break;
      case GameState.running:
        _effect.resume();
        break;
    }
  }

  @override
  void onCollision(Set<Vector2> intersectionPoints, PositionComponent other) {
    super.onCollision(intersectionPoints, other);
    if (other is! Aircraft || !gameRef.isRunning) {
      return;
    }
    removeFromParent();
  }
}
